﻿using System.Collections;
using System.Collections.Generic;
using TMPro;
using UnityEngine;
using UnityEngine.UI;

namespace Assets.Scripts.UI
{
    public class GamingPanel : BasePanel
    {
        [Header("Attenuation")]
        public float attenuationTime;
        public float attenuationT;
        [Header("Health")]
        public int curHealth = 0;
        public int maxHealth = 0;
        public Image healthBarBack;
        public Image healthBarFore;
        [Header("Player")]
        public Image playerCoolingImg;
        [Header("Weapon")]
        public Image weaponImg;
        public Image weaponCoolingImg;
        public TextMeshProUGUI weaponBulletNumberText;

        private WaitForSeconds attenuationSeconds;
        private Coroutine healthChangedCoro;
        public override void OnEnter()
        {
            base.OnEnter();
            curHealth = 0;
            maxHealth = 0;
            attenuationSeconds = new WaitForSeconds(attenuationTime);
        }
        public void EquipWeapon(Sprite weaponSprite)
        {
            weaponImg.sprite = weaponSprite;
        }
        public void LoseWeapon()
        {
            weaponImg.sprite = null;
        }
        public void UpdateWeaponBulletNumber(int numberNow, int numberTotal)
        {
            weaponBulletNumberText.SetText($"{numberNow}/{numberTotal}");
        }
        public void OnMaxHealthChanged(int maxHealth)
        {
            if (healthChangedCoro != null)
            {
                StopCoroutine(healthChangedCoro);
            }
            if ((float)curHealth / (this.maxHealth + 1) >= (float)curHealth / (maxHealth + 1))
            {
                healthChangedCoro = StartCoroutine(Hit_Coro(maxHealth, curHealth));
            }
            else if ((float)curHealth / (this.maxHealth + 1) < (float)curHealth / (maxHealth + 1))
            {
                healthChangedCoro = StartCoroutine(Recover_Coro(maxHealth, curHealth));
            }
            this.maxHealth = maxHealth;
        }
        public void OnCurHealthChanged(int curHealth)
        {
            if (healthChangedCoro != null)
            {
                StopCoroutine(healthChangedCoro);
            }
            if ((float)this.curHealth / (maxHealth + 1) >= (float)curHealth / (maxHealth + 1))
            {
                healthChangedCoro = StartCoroutine(Hit_Coro(maxHealth, curHealth));
            }
            else if ((float)this.curHealth / (maxHealth + 1) < (float)curHealth / (maxHealth + 1))
            {
                healthChangedCoro = StartCoroutine(Recover_Coro(maxHealth, curHealth));
            }
            this.curHealth = curHealth;
        }
        public void StartCoolingCoro(CoolingType ct, float coolingTime)
        {
            StartCoroutine(Cooling_Coro(ct, coolingTime));
        }
        IEnumerator Hit_Coro(int maxHealth, int healthNow)
        {
            float fillAmount = (float)healthNow / maxHealth;
            healthBarFore.fillAmount = fillAmount;
            while (healthBarBack.fillAmount > fillAmount + Mathf.Epsilon)
            {
                healthBarBack.fillAmount = fillAmount + (healthBarBack.fillAmount - fillAmount) * (1 - attenuationT);
                yield return attenuationSeconds;
            }
            healthBarBack.fillAmount = fillAmount;
        }
        IEnumerator Recover_Coro(int maxHealth, int healthNow)
        {
            float fillAmount = (float)healthNow / maxHealth;
            healthBarBack.fillAmount = fillAmount;
            while (healthBarFore.fillAmount < fillAmount - Mathf.Epsilon)
            {
                healthBarFore.fillAmount = healthBarFore.fillAmount + (fillAmount - healthBarFore.fillAmount) * (1 - attenuationT);
                yield return attenuationSeconds;
            }
            healthBarFore.fillAmount = fillAmount;
        }
        IEnumerator Cooling_Coro(CoolingType ct, float coolingTime)
        {
            float radio = attenuationTime / coolingTime;
            switch (ct)
            {
                case CoolingType.Player:
                    while (playerCoolingImg.fillAmount > 0)
                    {
                        playerCoolingImg.fillAmount -= radio;
                        yield return attenuationSeconds;
                    }
                    playerCoolingImg.fillAmount = 0;
                    break;
                case CoolingType.Weapon:
                    while (weaponCoolingImg.fillAmount > 0)
                    {
                        weaponCoolingImg.fillAmount -= radio;
                        yield return attenuationSeconds;
                    }
                    weaponCoolingImg.fillAmount = 0;
                    break;
                default:
                    break;
            }
        }
    }
}